package com.pactera.jep.service.sys.web.controller;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.pactera.jep.autoconfigure.web.controller.BaseRestController;
import com.pactera.jep.commons.CollectionUtils;
import com.pactera.jep.core.exception.ServiceException;
import com.pactera.jep.entity.Treeable;
import com.pactera.jep.service.sys.dto.UnitDto;
import com.pactera.jep.orm.Filter;
import com.pactera.jep.sys.code.UnitKind;
import com.pactera.jep.sys.model.Unit;
import com.pactera.jep.sys.service.UnitService;
import com.pactera.jep.web.code.WebCode;
import com.pactera.jep.web.entity.TreeNode;
import com.pactera.jep.web.util.TreeUtils;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import java.util.*;

@Api
@RestController
@RequestMapping("/unit")
public class UnitRestController extends BaseRestController {
    private static Logger logger = LoggerFactory.getLogger(UnitRestController.class);

    @Autowired
    UnitService unitService;

    /**
     * 获取当前用户能访问的菜单
     *
     * @return
     */
    @GetMapping("/load")
    public List<UnitDto> loadUnit(String unitCode) {
        List<Unit> units;
        if (StringUtils.isEmpty(unitCode)) {
            units = unitService.selectAll();
        } else {
            units = unitService.select(new Filter.Builder().like("pathCode", unitCode).build());
        }
        List<UnitDto> unitDtos = new ArrayList<UnitDto>();
        for (Unit unit : units) {
            UnitDto unitDto = new UnitDto();
            unitDto.setId(unit.getUnitCode());
            unitDto.setTitle(unit.getName());
            unitDto.setKind(unit.getKind());
            // 当获取本机构及下辖数据时，将本机构设置为根节点
            if (StringUtils.isNotBlank(unitCode) && unitCode.equals(unit.getUnitCode())) {
                unitDto.setParentId(null);
            } else {
                unitDto.setParentId(unit.getParentId());
            }
            unitDtos.add(unitDto);
        }
        return generateUnitDto(null, unitDtos);
    }

    private List<UnitDto> generateUnitDto(UnitDto parent, List<UnitDto> unitDtos) {

        List<UnitDto> data = new ArrayList<UnitDto>();

        for (UnitDto unitDto : unitDtos) {
            if (parent != null && parent.getId().equals(unitDto.getParentId())) {
                unitDto.setChildren(generateUnitDto(unitDto, unitDtos));
                data.add(unitDto);
            } else if (parent == null && StringUtils.isBlank(unitDto.getParentId())) {
                unitDto.setChildren(generateUnitDto(unitDto, unitDtos));
                data.add(unitDto);
            }
        }
        return data;
    }

    @PostMapping(value = "/selectPUnitDept")
    public String selectPUnitDept(String unitCode) {
        List<Unit> units = unitService.selectPUnitDept(unitCode);
        if (CollectionUtils.isNotEmpty(units)) {
            return JSONArray.toJSONString(units);
        }
        return null;
    }

    /**
     * 根据机构编码本机构下的所有部门，
     *
     * @return
     */
    @ApiOperation(value = "根据机构编码本机构下的所有部门，")
    @GetMapping(value = "/selectUnitDept")
    public String selectUnitDept(String unitCode) {
        List<Unit> units = unitService.selectUnitDept(unitCode);
        if (CollectionUtils.isNotEmpty(units)) {
            return JSONArray.toJSONString(units);
        }
        return null;
    }

    /**
     * 根据机构编码本机构下的所有部门，
     *
     * @return
     */
    @ApiOperation(value = "根据机构编码本机构下的所有部门，返回list")
    @GetMapping(value = "/selectUnitDept1")
    public List<Unit> selectUnitDept1(String unitCode) {
        //获取机构下的所有部门
        List<Unit> units = unitService.selectUnitDept(unitCode);
        if (CollectionUtils.isNotEmpty(units)) {
            return units;
        }
        return null;
    }

    /**
     * 根据机构编码本机构及下辖下的所有部门，
     *
     * @return
     */
    @ApiOperation(value = "根据机构编码本机构及下辖下的所有部门，")
    @GetMapping(value = "/selectUnitAllOrDeptAll")
    public String selectUnitAllOrDeptAll(String unitCode) {
        List<Unit> units = unitService.selectUnitAllOrDeptAll(unitCode);
        if (CollectionUtils.isNotEmpty(units)) {
            return JSONArray.toJSONString(units);
        }
        return null;
    }

    /**
     * 根据机构编码查询上级主管部门，
     *
     * @return
     */
    @ApiOperation(value = "根据机构编码查询上级主管部门，")
    @GetMapping(value = "/selectHeadDept")
    public String selectHeadDept(String unitCode) {
        List<Unit> units = unitService.selectHeadDept(unitCode);
        if (CollectionUtils.isNotEmpty(units)) {
            return JSONArray.toJSONString(units);
        }
        return null;
    }

    /**
     * 查询当前数据库中存在的机构层级，
     *
     * @return
     */
    @ApiOperation(value = "查询当前数据库中存在的机构层级，")
    @GetMapping(value = "/selectExistedHierarchy")
    public String selectExistedHierarchy() {
        List<String> hierarchys = unitService.selectExistedHierarchy();
        if (CollectionUtils.isNotEmpty(hierarchys)) {
            return JSONArray.toJSONString(hierarchys);
        }
        return null;
    }

    @PostMapping(value = "/select")
    public String select(String unitFilters) {
        List<Filter> filterList = new ArrayList<>();
        if (org.apache.commons.lang.StringUtils.isNotBlank(unitFilters)) {
            filterList = JSONArray.parseArray(unitFilters, Filter.class);
        }
        List<Unit> units = unitService.select(filterList);
        if (CollectionUtils.isNotEmpty(units)) {
            return JSONArray.toJSONString(units);
        }
        return null;
    }

    /**
     * to expire
     * 点击树时查看当前节点的详细信息，
     *
     * @return
     */
    @ApiOperation(value = "点击树时查看当前节点的详细信息，")
    @GetMapping(value = "/getAgencyTree")
    public Map<String, Object> getAgencyTree(String unitCode) {
        //定义返回的结果集
        Map<String, Object> result = new HashMap<String, Object>();
        //当前机构
        Unit unit = unitService.get(new Filter.Builder().eq("unitCode", unitCode).build());
        //当前机构父机构
        Unit unitParent = new Unit();
        if (unit != null && unit.getParentId() != null) {
            unitParent = unitService.get(new Filter.Builder().eq("unitCode", unit.getParentId()).build());
        }
        result.put("unitNode", unit);
        result.put("unitParent", unitParent);
        return result;
    }

    /**
     * to expire
     * 更改当前机构的信息，
     *
     * @return
     */
    @ApiOperation(value = "更改当前机构的信息，")
    @PostMapping(value = "/saveUnit")
    public Map<String, Object> saveUnit(@RequestBody Unit unit) {
        Map<String, Object> tips = new HashMap<String, Object>();
        try {
            unitService.updateUnit(unit);
            tips.put(WebCode.SUCCESS, true);
            tips.put(WebCode.MSG, WebCode.SUCCESS_SAVE);
        } catch (ServiceException e) {
            logger.info(e.getMessage());
            tips.put(WebCode.SUCCESS, false);
            tips.put(WebCode.MSG, WebCode.FAILURE_SAVE);
        }
        return tips;
    }

    @ApiOperation(value = "验证提交的编码是否已经存在数据库中")
    @GetMapping(value = "/check", produces = "application/json;charset=UTF-8")
    public Map<String, Object> check(String code) {
        Map<String, Object> tips = new HashMap<String, Object>();

        Boolean exist = unitService.exists(code);
        tips.put("valid", !exist);

        return tips;
    }

    /**
     * 移除Unit节点
     *
     * @param unitCode
     * @return
     */
    @ApiOperation(value = "移除节点")
    @DeleteMapping(value = "/removeNode/{unitCode}")
    public Map<String, Object> removeNode(@PathVariable String unitCode) {
        Map<String, Object> tips = new HashMap<String, Object>();

        /*查询当前节点是否有子节点*/
        long count = unitService.count(new Filter.Builder().eq("parentId", unitCode).build());

        /*总数大于0，提示先删除子节点，反之进行删除*/
        if (count > 0) {
            tips.put(WebCode.SUCCESS, false);
            tips.put(WebCode.MSG, WebCode.DELETE_SUBNODE_FIRST);
        } else {
            try {
                unitService.deleteByPrimaryKey(unitCode);
                tips.put(WebCode.SUCCESS, true);
                tips.put(WebCode.MSG, WebCode.SUCCESS_DELETE);
            } catch (ServiceException e) {
                logger.info(e.getMessage());
                tips.put(WebCode.SUCCESS, false);
                tips.put(WebCode.MSG, WebCode.FAILURE_DELETE);
            }

        }
        return tips;
    }

    /**
     * 新增节点
     *
     * @param unit
     * @return
     */
    @ApiOperation(value = "新增节点")
    @PostMapping(value = "/updateNode")
    public Map<String, Object> updateNode(@RequestBody Unit unit) {
        Map<String, Object> tips = new HashMap<String, Object>();
        try {
            /*调用更新机构方法*/
            unitService.updateUnit(unit);

            tips.put(Treeable.TREE_ID, unit.getUnitCode());
            tips.put(WebCode.SUCCESS, true);
            tips.put(WebCode.MSG, WebCode.SUCCESS_SAVE);
        } catch (Exception ex) {
            logger.info(ex.getMessage());
            tips.put(WebCode.SUCCESS, false);
            tips.put(WebCode.MSG, WebCode.FAILURE_SAVE);
        }
        return tips;
    }

    /**
     * 异步初始化加载数据
     *
     * @param parentId
     * @param request
     * @return
     */
    @ApiOperation(value = "异步加载数据")
    @GetMapping(value = "/treeNode")
    public List<TreeNode> treeNode(String parentId, HttpServletRequest request) {
        List<Filter> filters = null;

        if (parentId == null) {
            filters = new Filter.Builder().nl("parentId").build();
        } else {
            filters = new Filter.Builder().eq("parentId", parentId).build();
        }

        List<Unit> list = unitService.select(filters);
        String[] columns = new String[]{
                "unitCode",
                "unitName",
                "unitDesc",
                "displayName",
                "isBizDept",
                "bizTypeCode",
                "bizTypeName",
                "hierarchy",
                "kind",
                "owner",
                "pathCode",
                "pathName",
                "level",
                "parentId",
                "areaCode",
                "fax",
                "mailCode",
                "officeAddr",
                "postCode",
                "telphone",
                "status",
        };

        List<TreeNode> nodes = TreeUtils.parse(list, columns);
        return nodes;
    }

    /**
     * 验证当前机构的机构类型是否为ORG
     *
     * @param unitCode 机构编码
     * @return
     */
    @ApiOperation(value = "验证当前机构的机构类型是否为ORG")
    @GetMapping(value = "/isOrg/{unitCode}")
    public Map<String, Object> isOrg(@PathVariable String unitCode) {

        Map<String, Object> tips = new HashMap<String, Object>();
        Unit unit = unitService.get(unitCode);
        if (unit != null) {
            if (UnitKind.UNIT.name().equals(unit.getKind())) {
                tips.put("valid", true);
            } else {
                tips.put("valid", false);
            }
        }
        return tips;
    }

    /**
     * 根据机构编码本查询当前机构，
     *
     * @return
     */
    @ApiOperation(value = "根据机构编码查询当前机构")
    @GetMapping(value = "/selectUnitByCode")
    public Map<String, Object> selectUnitByCode(String unitCode) {

        Map<String, Object> map = new HashMap<String, Object>();

        Unit unit = unitService.get(unitCode);
        if (unit != null) {
            map.put("unit", unit);
            map.put(WebCode.SUCCESS, true);
        } else {
            map.put(WebCode.SUCCESS, false);
        }
        return map;

    }


}
